<template>
  <el-table-column v-if="isShowField()" :sortable="!!col.sortable" :prop="col.prop" :label="col.label" :width="col.width || 'auto'" :header-align="col.headerAlign || 'left'" :align="col.align || 'left'" :filters="col.filters" :filter-method="col.filterMethod" :filtered-value="filteredValue" class-name="col-container">
    <template slot-scope="{ row, column, $index }">
      <!--通用列插槽-->
      <slot :row="row" :col="col" :index="$index" name="column-slot">
        <template v-if="!col.readonly && !disabled && col.type=='input' && row===currentRow">
          <el-switch v-if="['byte'].indexOf(col.dataType)>=0" :ref="'switch-'+col.prop" :key="col.key" v-model="row[col.prop]" active-value="1" inactive-value="0" size="mini" @change="(val)=>{change($refs['switch-' + col.prop], val, row, col);}"></el-switch>
          <el-input-number v-else-if="['int32', 'int64'].indexOf(col.dataType)>=0" :ref="'input-number-'+col.prop" :key="col.key" v-model.number="row[col.prop]" :style="{width:'100%'}" controls-position="right" size="mini" @change="(val)=>{change($refs['input-number-' + col.prop], val, row, col);}"></el-input-number>
          <el-input v-else-if="['decimal', 'double', 'money'].indexOf(col.dataType)>=0" :ref="'input-'+col.prop" :key="col.key" v-model="row[col.prop]" :style="{width:'100%'}" :step="step(col)" size="mini" type="number" @change="(val)=>{change($refs['input-' + col.prop], val, row, col);}"></el-input>
          <el-input v-else :ref="'select-'+col.prop" :key="col.key" v-model="row[col.prop]" :style="{width:'100%'}" size="mini" @change="(val)=>{change($refs['input-' + col.prop], val, row, col);}"></el-input>
        </template>

        <el-cascader v-else-if="!col.readonly && !disabled && col.type=='cascader' && row===currentRow" :ref="'cascader-'+col.prop" :key="col.key" v-model="row[col.prop]" :options="col" :style="{width:'100%'}" size="mini" @change="(val)=>{change($refs['cascader-' + col.prop], val, row, col);}"></el-cascader>

        <el-select v-else-if="!col.readonly && !disabled && col.type=='select' && row===currentRow" :ref="'select-'+col.prop" :key="col.key" v-model="row[col.prop]" :style="{width:'100%'}" :field="col" :filterable="!!col.filterable" :multiple="col.multiple" :allow-create="col.allowCreate" :clearable="col.clearable" size="mini" @change="(val)=>{change($refs['select-' + col.prop], val, row, col);}">
          <el-option v-for="item in getOptions(col)" :key="item.id" v-bind="item" :label="item.label" :value="item.value" :option="item" @change="(val)=>{change($refs['input-' + col.prop], val, row, col);}">
          </el-option>
        </el-select>

        <template v-else-if="!col.readonly && !disabled && col.type === 'time' && row===currentRow">
          <el-time-picker :ref="'time-picker-'+col.prop" :key="col.key" v-model="row[col.prop]" :is-range="col.isRange" :placeholder="col.placeholder" :start-placeholder="col.startPlaceholder" :end-placeholder="col.endPlaceholder" :readonly="col.readonly" :disabled="col.disabled" :editable="col.editable" :clearable="col.clearable" :arrow-control="col.arrowControl" :style="{width: col.width}" size="mini" @change="(val)=>{change($refs['time-picker-' + col.prop], val, row, col);}">
          </el-time-picker>
        </template>

        <template v-else-if="!col.readonly && !disabled && ['date', 'datetime'].indexOf(col.type)>=0 && row===currentRow">
          <el-date-picker :ref="'date-picker-'+col.prop" :key="col.key" v-model="row[col.prop]" :type="col.type" :is-range="col.isRange" :placeholder="col.placeholder" :start-placeholder="col.startPlaceholder" :end-placeholder="col.endPlaceholder" :readonly="col.readonly" :disabled="col.disabled" :editable="col.editable" :clearable="col.clearable" :format="col.format" :value-format="col.format" class="w-100pc" size="mini" @change="(val)=>{change($refs['date-picker-' + col.prop], val, row, col);}">
          </el-date-picker>
        </template>

        <!-- 输入选择框 -->
        <template v-else-if="!col.readonly && !disabled && col.type === 'input-select' && row===currentRow">
          <input-select v-model="row[col.prop]" :field="col" :options="[]" :props="{label:col.options.labelField, value:col.options.valueField}" :label="col.label" :disabled="getInputSelectOptions(col).disabled" :input-width="getInputSelectOptions(col).width" :placeholder="getInputSelectOptions(col).placeholder" :load-data-before="loadDataBefore" @on-item-click="(ref, val, itemData)=>{itemClick(ref, val, itemData, col);}" @on-change="(ref, val)=>{change(ref, val, col, row);}">
          </input-select>
        </template>

        <!-- 表格选择框 -->
        <template v-else-if="!col.readonly && !disabled && col.type === 'table-select' && row===currentRow">
          <table-select v-model="row[col.prop]" :form-data="row" :field="col" :columns="col.options.columns" :label="col.label" :disabled="disabled" :input-width="col.options.width" :placeholder="col.options.placeholder" @on-focus="(ref, val, event)=>{onFocus(ref, val, event, col);}" @on-item-click="(ref, val, itemData)=>{itemClick(ref, val, itemData, col);}" @on-change="(ref, val)=>{change(ref, val, row, col);}" @on-key-up="(ref, val, event, tableData)=>{onKeyup(ref, val, event, col, tableData);}" @on-row-change="(ref, selectedRow) => {onRowChange(ref, selectedRow, col);}" @on-row-click="(ref, selectedRow) => {onRowClick(ref, selectedRow, col);}">
          </table-select>
        </template>

        <template v-else>
          <template v-if="col.prop==dataOptions.linkColumn">
            <el-link type="primary" @click.native="()=>{linkEditor(row[dataOptions.idField]);}">{{ row[col.prop] }}</el-link>
          </template>
          <template v-else-if="col.options && (col.options.dropdown_Id>0 || col.options.remote===false)">
            {{ translateText(col, row[col.prop], col.options.dropdown_Id) }}
          </template>
          <template v-else>
            <!-- 通用标签颜色着色 -->
            <template v-if="col.tagColorList && col.tagColorList.length && row[col.prop]!==undefined">
              <el-tag :color="common.getTagBgColor(row, col, row[col.prop])" :style="common.getTagColor(row, col, row[col.prop])">
                {{ common.formatData(row, col) }}
              </el-tag>
            </template>
            <template v-else>
              {{ common.formatData(row, col) }}
            </template>
          </template>
        </template>
      </slot>
    </template>
  </el-table-column>
</template>

<script>
import InputSelect from "@/components/base/InputSelect";
import TableSelect from "@/components/base/TableSelect";

export default {
  name: "yrt-editor-input",
  components: {
    InputSelect,
    TableSelect,
  },
  props: {
    // 列数据对象
    col: {
      type: Object,
      required: true,
      default: () => {
        return {};
      },
    },
    // 数据参数
    dataOptions: {
      type: Object,
      default: () => {},
    },
    // 下拉框值集合
    dropdownData: {
      type: Object,
      default: () => {},
    },
    // 是否禁用
    disabled: {
      type: Boolean,
      default: false,
    },
    // 控制显示字段,true=显示所有字段，Array=只显示数组内的字段
    showFields: {
      type: [Boolean, Array],
      default: true,
    },
    // 自定义查询条件
    filteredValue: {
      type: Array,
      default: () => {
        return [];
      },
    },
    // 当前行
    currentRow: {
      type: Object,
      default: () => {},
    },
    // 输入选择框加载前方法
    loadDataBefore: {
      type: Function,
      default: () => {
        return () => {};
      },
    },
  },
  data() {
    return {};
  },
  computed: {
    // 是否禁用
    currentDisabled: {
      get: function () {
        return this.disabled;
      },
      set: function (newValue) {
        this.$emit("update:disabled", newValue); // 双向绑定prop.action，通知父级组件变量值同步更新
      },
    },
    // 获得下拉框options
    getOptions: {
      get: function () {
        var the = this;
        return function (field) {
          const dropdown_Id =
            field.options && field.options.dropdown_Id
              ? field.options.dropdown_Id
              : field.dropdown_Id;
          let options = [];
          if (dropdown_Id) {
            options = the.dropdownData["dropdown" + dropdown_Id];
          } else {
            if (field.options) {
              options = field.options.options;
            }
          }
          return options;
        };
      },
    },
    // 获得输入选择框options
    getInputSelectOptions: {
      get: function () {
        var the = this;
        return function (field) {
          if (field.options.remote === "bindDropdown") {
            field.options.options =
              the.dropdownData["dropdown" + field.options.dropdown_Id];
          }
          return field.options;
        };
      },
    },
    // 数字输入步长
    step: {
      get: function () {
        return function (field) {
          let len = 1;
          if (field.formatter) {
            const arr = field.formatter.split(".");
            len =
              arr.length <= 1
                ? 1
                : Math.Round(Math.pow(0.1, arr[1].length), arr[1].length);
          }
          return len;
        };
      },
    },
  },
  watch: {
    currentRow: {
      handler(newVal, oldVal) {
        const col = this.col;
        // 将多选值下拉框转为数组
        if (col.multiple && newVal) {
          const v = newVal[col.prop];
          if (v) {
            if (!Array.isArray(v)) {
              const items = v.split("/");
              newVal[col.prop] = [];
              for (const item of items) {
                this.$set(newVal[col.prop], newVal[col.prop].length, item);
              }
            }
          } else {
            newVal[col.prop] = [];
          }
        }
        if (col.multiple && !newVal && oldVal) {
          const v = oldVal[col.prop];
          if (Array.isArray(v)) {
            oldVal[col.prop] = v.join("/");
          } else {
            oldVal[col.prop] = v;
          }
        }
      },
      immediate: true,
    },
  },
  created() {
    this.loadCascaderData();
  },
  mounted() {},
  destroyed() {},
  methods: {
    // 是否显示字段
    isShowField() {
      let isShow = this.col.prop !== "_action" && !this.col.hidden;
      if (
        !(
          this.showFields === true ||
          (Array.isArray(this.showFields) &&
            this.showFields.indexOf(this.col.prop) >= 0)
        )
      ) {
        isShow = false;
      }

      return isShow;
    },
    // 字段change事件
    change(ref, val, row, field) {
      var the = this;
      if (field.type === "select") {
        // 设置表单数据，附加下拉框其他字段，非多选时使用
        if (!Array.isArray(val)) {
          const optInfo = ref.getOption(val);
          if (optInfo && optInfo.$attrs) {
            var itemOption = optInfo.$attrs.option;
            Object.keys(itemOption).forEach((key, index) => {
              if (["value", "label"].indexOf(key) < 0) {
                the.$set(row, key, itemOption[key]);
              }
            });
          } else {
            the.$set(row, field.prop, val);
          }
        }
      }
      if (["decimal", "double"].indexOf(field.dataType) >= 0) {
        row[field.prop] = Number(val);
      }
      this.$emit("on-detail-change", ref, val, row, field);
      // 自定义
    },
    // 翻译下拉框值
    translateText(col, val, dropdown_Id) {
      if (col.options.remote === false) {
        const ddList = col.options.options;
        if (!ddList) return val;
        const item = ddList.find((item, index, arr) => {
          return item.value === val;
        });
        if (!item) return val;
        return item.label;
      } else {
        const ddList = this.dropdownData["dropdown" + dropdown_Id];
        if (!ddList) return val;
        const item = ddList.find((item, index, arr) => {
          return item.value === val;
        });
        if (!item) return val;
        return item.label;
      }
    },
    // 树形下拉框获得点击项
    onTreeNodeClick(data, node, el, field) {
      var the = this;
      // 仅选择叶节点
      if (!node.isLeaf && field.options.onlySelectLeaf) return;

      var key = field.options.prop;
      // 将下拉框中的值赋给表单
      if (Object.keys(data).findIndex((item) => item === key) >= 0) {
        Object.keys(data).forEach((key, index) => {
          if (
            [
              "value",
              "label",
              "hasChild",
              "hasFactChild",
              "state",
              "attributes",
            ].indexOf(key) < 0
          ) {
            the.$set(the.formData, key, data[key]);
          }
        });
      } else {
        the.$set(the.formData, key, data[key]);
      }
    },
    // 加载级联数据
    loadCascaderData() {
      var the = this;
      this.$nextTick(() => {
        Object.keys(this.$refs).forEach((refName) => {
          if (refName.indexOf("cascader") >= 0) {
            var ref = the.$refs[refName];
            var field = ref.$attrs["field"];
            the.$emit("on-focus", ref, null, field);
          }
        });
      });
    },
    // 树形输入框load
    treeLoad(node, resolve, subField) {
      var the = this;
      this.$emit("tree-load", node, resolve, subField);
      // 默认加载数据
      if (!subField.isLoaded) {
        var keyName = subField.ajaxParams.keyName;
        if (!keyName) {
          the.$message.error("未设置tree下拉框ajax加载参数！");
          return;
        }
        // the.$nextTick(() => {
        //   var where = "";
        //   var userInfo = this.common.getUserInfo();
        //   if (node.level === 0) {
        //     where = `UserProduct_Id=${userInfo.UserProduct_Id} And ParentId=0`;
        //   } else {
        //     where = `UserProduct_Id=${userInfo.UserProduct_Id} And ParentId=${node.data[subField.ajaxParams.keyName]}`;
        //   }

        //   var url = "/api/common/loadTreeNode";
        //   var params = subField.ajaxParams;
        //   params.where = where;
        //   the.common.ajax(
        //     url,
        //     params,
        //     res => {
        //       if (res.result) {
        //         resolve(res.data);
        //       } else {
        //         the.$message.error(res.Msg);
        //       }
        //     },
        //     true
        //   );
        // });
      }
    },
    // input-select item click event
    itemClick(ref, val, itemData, field, row) {
      this.$emit("on-item-click", ref, val, itemData, field, row);
    },
    // 获得焦点
    onFocus(ref, val, event, field) {
      this.$emit("detail-on-focus", ref, val, event, field);
    },
    // 按键抬起
    onKeyup(ref, val, event, field, tableData) {
      // if (["decimal"].indexOf(field.options.dataType) >= 0) {
      //   this.formData[field.options.prop] = Number(val);
      // }
      this.$emit("detail-on-key-up", ref, val, event, field, tableData);
    },
    // 按键抬起
    onKeyDown(ref, val, event, field, tableData) {
      this.$emit("detail-on-key-down", ref, val, event, field, tableData);
    },
    // 获得tableSelect行改变
    onRowChange(ref, selectedRow, field) {
      this.$emit("detail-on-row-change", ref, selectedRow, field);
    },
    // 获得tableSelect行单击事件
    onRowClick(ref, selectedRow, field) {
      this.$emit("detail-on-row-click", ref, selectedRow, field);
    },
  },
};
</script>

<style rel="stylesheet/scss" lang="scss" scoped>
.col-container {
  padding: 0px;
}
</style>
